# pita: An invisible audio player
# Copyright (C) 2006-2007 Austin Bingham
#
# This program is free software# you can redistribute it and/or
# modify it under the terms of the GNU General Public License
# as published by the Free Software Foundation# either version 2
# of the License, or (at your option) any later version.
#
# This program is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY# without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
# GNU General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with this program# if not, write to the Free Software
# Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA  02111-1307, USA.
#
# You can reach the author at:
#     austin.bingham@gmail.com

import re, urllib

'''
a collection of routines for working with m3u files.
'''

extinf_re = re.compile('^#EXTINF:')

def throw(filename):
    raise IOError('%s does not appear to be a valid M3U file' % filename)

def parse_m3u(u):
    '''
    parses a file as an M3U playlist, returning a
    possibly empty list of filenames. If there is
    a problem parsing this file, this throws IOError.
    '''
    data = [l.strip() for l in u.readlines()]
    rval = []
    try:
        start_idx = data.index('#EXTM3U') + 1
    except ValueError:
        throw(u.geturl())
        
    for idx in range(start_idx, len(data), 2):
        if idx >= len(data):
            throw(u.geturl())
        elif not extinf_re.match(data[idx]):
            throw(u.geturl())
        else:
            rval.append(data[idx + 1])

    return rval
    
def expand_filelist(files):
    '''
    Expands m3u files into lists of filenames. Given a list
    of filenames, this looks for any that appear to be
    m3u files. For any m3u lists, this expands that entry into
    the files referenced in the playlist. Invalid playlists are
    silently ignored.
    '''
    rval = []
    for f in files:
        try:
            u = urllib.urlopen(f)
            if u.info()['content-type'] == 'audio/x-mpegurl':
                rval += parse_m3u(u)
            else:
                rval.append(f)
        except IOError:
            print 'error'
            rval.append(f)

    return rval
